﻿using EMall.Domain;
using System.Text.Json;

namespace EMall.OrderService.Orders
{
    public class Order : AggregateRoot<int>
    {
        public string OrderNumber { get; private set; }
        public Buyer Buyer { get; private set; }
        public Address Address { get; private set; }
        public OrderStatus Status { get; private set; }
        public List<OrderItem> OrderItems { get; private set; }
        public DateTime CreatedTime { get; private set; }
        protected Order() { }
        public Order(Buyer buyer, Address address)
        {
            Buyer = buyer;
            Address = address;
            Status = OrderStatus.Created;
            CreatedTime = DateTime.Now;
            AddDomainEvent(new EntityCreatedDomainEvent<Order>(this));
        }
        public void Update(Buyer buyer, Address address)
        {
            var originJson = JsonSerializer.Serialize(this);
            Buyer = buyer;
            Address = address;
            AddDomainEvent(new EntityUpdatedDomainEvent<Order>(originJson, this));
        }
        public void AddOrderItem(int productId, string productName, decimal unitPrice, int quantity)
        {
            var existingOrderItem = OrderItems.SingleOrDefault(o => o.ProductId == productId);
            if (existingOrderItem != null)
            {
                existingOrderItem.AddQuantity(quantity);
            }
            else
            {
                var orderItem = new OrderItem(Id, productId, productName, unitPrice, quantity);
                OrderItems.Add(orderItem);
            }
        }
        public void SetPaidStatus()
        {
            if (Status == OrderStatus.Created)
            {
                Status = OrderStatus.Paid;
            }
        }
        public void SetShippedStatus()
        {
            if (Status == OrderStatus.Paid)
            {
                Status = OrderStatus.Shipped;
            }
        }
        public void SetReceivedStatus()
        {
            if (Status == OrderStatus.Shipped)
            {
                Status = OrderStatus.Received;
            }
        }
        public void SetCompletedStatus()
        {
            if (Status == OrderStatus.Received)
            {
                Status = OrderStatus.Completed;
            }
        }
        public void SetRefundedStatus()
        {
            Status = OrderStatus.Refunded;
        }
        public void SetCancelledStatus()
        {
            if (Status == OrderStatus.Created)
            {
                Status = OrderStatus.Cancelled;
            }
        }
        public decimal GetTotal() => OrderItems.Sum(o => o.UnitPrice * o.Quantity);
    }
}
